package com.qujia.fleet.service.impl;

import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.qujia.common.constant.UserConstants;
import com.qujia.common.core.domain.UniversalRedisMessageDto;
import com.qujia.common.core.domain.entity.SysUser;
import com.qujia.common.core.domain.model.LoginUser;
import com.qujia.common.enums.WxConsumptionMessageEnum;
import com.qujia.common.exception.CustomException;
import com.qujia.common.utils.SecurityUtils;
import com.qujia.fleet.domain.FleetCard;
import com.qujia.fleet.domain.FleetCardAllocationRecoveryRecord;
import com.qujia.fleet.domain.FleetCardRechargeRecord;
import com.qujia.fleet.domain.FleetCardSub;
import com.qujia.fleet.domain.form.FleetCardForm;
import com.qujia.fleet.domain.form.FleetCardQueryForm;
import com.qujia.fleet.domain.form.FleetCardRechargeForm;
import com.qujia.fleet.domain.vo.FleetCardVo;
import com.qujia.fleet.enums.CardRechargeRecordEnum;
import com.qujia.fleet.mapper.FleetCardMapper;
import com.qujia.fleet.service.FleetCardAllocationRecoveryRecordService;
import com.qujia.fleet.service.FleetCardRechargeRecordService;
import com.qujia.fleet.service.FleetCardService;
import com.qujia.fleet.service.FleetCardSubService;
import com.qujia.fleet.utils.OrderNoUtil;
import com.qujia.station.domain.Enterprise;
import com.qujia.station.domain.SysAppUserInfo;
import com.qujia.station.domain.dto.BalanceChangeWxNotifyDTO;
import com.qujia.station.domain.vo.EnterpriseAndStationVo;
import com.qujia.station.mapper.AppUserInfoMapper;
import com.qujia.station.service.IEnterpriseService;
import com.qujia.station.service.IStationService;
import com.qujia.system.domain.vo.SysEnterpriseAndStationVo;
import org.apache.commons.lang3.ObjectUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.math.BigDecimal;
import java.util.*;

@Service
public class FleetCardServiceImpl implements FleetCardService {

    @Autowired
    private FleetCardMapper fleetCardMapper;

    @Autowired
    private FleetCardRechargeRecordService fleetCardRechargeRecordService;

    @Autowired
    private FleetCardSubService fleetCardSubService;

    @Autowired
    private FleetCardAllocationRecoveryRecordService fleetCardAllocationRecoveryRecordService;

    @Autowired
    private AppUserInfoMapper appUserInfoMapper;

    @Autowired
    private IEnterpriseService enterpriseService;

    @Autowired
    private IStationService stationService;

    @Autowired
    private RedisTemplate redisTemplate;

    @Value("${message.channel}")
    private String channel;

    @Override
    public int insertFleetCard(FleetCardForm fleetCardForm) {
        if (ObjectUtils.notEqual(SecurityUtils.getLoginUser().getUser().getUserLevel(), "1"))
            throw new CustomException("请使用油企账号添加！");

        LoginUser loginUser= SecurityUtils.getLoginUser();
        Long enterpriseId = loginUser.getUser().getEnterpriseId();

        FleetCardQueryForm fleetCardQueryForm=new FleetCardQueryForm();
        fleetCardQueryForm.setPhone(fleetCardForm.getPhone());
        fleetCardQueryForm.setEnterpriseId(enterpriseId);

        List<FleetCardVo> fleetCardVos = fleetCardMapper.selectFleetCardList(fleetCardQueryForm);
        if(fleetCardVos.size()>0){
            throw new CustomException("该手机号已经申请了车队");
        }
        Map<String,Object> params=new HashMap<>();
        params.put("mobilePhone",fleetCardForm.getPhone());
        params.put("stationId",enterpriseId);
        List<SysAppUserInfo> sysAppUserInfos = appUserInfoMapper.selectAppUserInfoByPhoneAndStationId(params);
        if(sysAppUserInfos.size()>0){
            FleetCardSub fleetCardSubQuery=new FleetCardSub();
            fleetCardSubQuery.setAppUserId(sysAppUserInfos.get(0).getUserId());
            fleetCardSubQuery.setEnterpriseId(enterpriseId);
            List<FleetCardSub> FleetCardSubs=fleetCardSubService.query(fleetCardSubQuery);
            if(FleetCardSubs.size()>0){
                throw new CustomException("该手机号已经申请加入了车队");
            }
        }
        FleetCard fleetCard = new FleetCard();
        BeanUtils.copyProperties(fleetCardForm, fleetCard);
        fleetCard.setEnterpriseId(SecurityUtils.getLoginUser().getUser().getEnterpriseId());
        fleetCard.setCardNumber("101" + System.currentTimeMillis()); // 前缀101代表车队卡
        fleetCard.setCreatedBy(SecurityUtils.getUsername());
        fleetCard.setUpdatedBy(SecurityUtils.getUsername());
        if (null != fleetCardForm.getUseType() && 1 == fleetCardForm.getUseType()) {//核销方式为 1司机自动出示核销码
            fleetCard.setSecondaryCardAllocationType(1);//默认设置 1.共享主卡额度
        }
        return fleetCardMapper.insertFleetCard(fleetCard);
    }

    @Override
    public int updateFleetCard(Long id, FleetCardForm fleetCardForm) {
        if (ObjectUtils.notEqual(SecurityUtils.getLoginUser().getUser().getUserLevel(), "1"))
            throw new CustomException("请使用油企账号修改！");


        FleetCard fleetCard = new FleetCard();
        BeanUtils.copyProperties(fleetCardForm, fleetCard);
        fleetCard.setId(id);
        fleetCard.setUpdatedTime(new Date());
        fleetCard.setUpdatedBy(SecurityUtils.getUsername());

        //修改手机号判断手机号是否在车队卡中存在
        LoginUser loginUser= SecurityUtils.getLoginUser();
        Long enterpriseId = loginUser.getUser().getEnterpriseId();
        FleetCardQueryForm fleetCardQuery = new FleetCardQueryForm();
        fleetCardQuery.setPhone(fleetCardForm.getPhone());
        fleetCardQuery.setEnterpriseId(enterpriseId);
        List<FleetCardVo> fleetCardVos = fleetCardMapper.selectFleetCardList(fleetCardQuery);
        for (FleetCardVo fleetCardVo : fleetCardVos) {
            if(!fleetCardVo.getId().equals(id)){
                throw new CustomException("已存在相同的联系方式");
            }
        }
        //手机号是否在子卡中存在

        Map<String,Object> params=new HashMap<>();
        params.put("mobilePhone",fleetCardForm.getPhone());
        params.put("stationId",enterpriseId);
        List<SysAppUserInfo> sysAppUserInfos = appUserInfoMapper.selectAppUserInfoByPhoneAndStationId(params);
        if(sysAppUserInfos.size()>0){
            FleetCardSub fleetCardSubQuery=new FleetCardSub();
            fleetCardSubQuery.setAppUserId(sysAppUserInfos.get(0).getUserId());
            fleetCardSubQuery.setEnterpriseId(fleetCardForm.getEnterpriseId());
            List<FleetCardSub> FleetCardSubs=fleetCardSubService.query(fleetCardSubQuery);
            if(FleetCardSubs.size()>0){
                throw new CustomException("该手机号已经申请了车队");
            }
        }

        return fleetCardMapper.updateFleetCard(fleetCard);
    }

    @Override
    public int updateFleetCard(FleetCard fleetCard) {
        return fleetCardMapper.updateFleetCard(fleetCard);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public int updateFleetCardRecharge(Long id, FleetCardRechargeForm fleetCardRechargeForm) {
        if (ObjectUtils.notEqual(SecurityUtils.getLoginUser().getUser().getUserLevel(), "1"))
            throw new CustomException("请使用油企账号操作！");

        FleetCard fleetCard = fleetCardMapper.selectFleetCardById(id);
        if (ObjectUtils.isEmpty(fleetCard)) throw new CustomException("记录不存在！");

        if(Objects.isNull(fleetCardRechargeForm.getGiftAmount())){
            fleetCardRechargeForm.setGiftAmount(BigDecimal.ZERO);
        }
        FleetCard updateFleetCard = new FleetCard();
        if(CardRechargeRecordEnum.MANUAL_SUB.getValue().equals(fleetCardRechargeForm.getCardType())){
            updateFleetCard.setBalance(fleetCard.getBalance().subtract(fleetCardRechargeForm.getRechargeAmount()).subtract(fleetCardRechargeForm.getGiftAmount()));
            updateFleetCard.setRechargeAmount(fleetCard.getRechargeAmount().subtract(fleetCardRechargeForm.getRechargeAmount()));
            updateFleetCard.setGiftAmount(fleetCard.getGiftAmount().subtract(fleetCardRechargeForm.getGiftAmount()));
        } else {
            updateFleetCard.setBalance(fleetCard.getBalance().add(fleetCardRechargeForm.getRechargeAmount()).add(fleetCardRechargeForm.getGiftAmount()));
            updateFleetCard.setRechargeAmount(fleetCard.getRechargeAmount().add(fleetCardRechargeForm.getRechargeAmount()));
            updateFleetCard.setGiftAmount(fleetCard.getGiftAmount().add(fleetCardRechargeForm.getGiftAmount()));
        }
        updateFleetCard.setId(id);
        updateFleetCard.setUpdatedTime(new Date());
        updateFleetCard.setUpdatedBy(SecurityUtils.getUsername());
        updateFleetCard.setEnterpriseId(fleetCard.getEnterpriseId());
        updateFleetCard.setPhone(fleetCard.getPhone());
        updateFleetCard.setCardNumber(fleetCard.getCardNumber());
        fleetCardMapper.updateFleetCard(updateFleetCard);

        // 推送消息
        if("1".equals(fleetCardRechargeForm.getIsPush())){
            pushMessage(updateFleetCard, fleetCardRechargeForm);
        }


        FleetCardRechargeRecord fleetCardRechargeRecord = new FleetCardRechargeRecord();
        fleetCardRechargeRecord.setFleetCardId(id);
        fleetCardRechargeRecord.setEnterpriseId(fleetCard.getEnterpriseId());
        fleetCardRechargeRecord.setRechargeAmount(fleetCardRechargeForm.getRechargeAmount());
        fleetCardRechargeRecord.setGiftAmount(fleetCardRechargeForm.getGiftAmount());
        fleetCardRechargeRecord.setBalance(fleetCard.getBalance());
        fleetCardRechargeRecord.setAfterBalance(updateFleetCard.getBalance());
        fleetCardRechargeRecord.setUpdatedBy(SecurityUtils.getUsername());
        fleetCardRechargeRecord.setCreatedBy(SecurityUtils.getUsername());
        fleetCardRechargeRecord.setStationId(fleetCardRechargeForm.getStationId());
        fleetCardRechargeRecord.setCardType(fleetCardRechargeForm.getCardType());
        fleetCardRechargeRecord.setNotes(fleetCardRechargeForm.getNotes());
        fleetCardRechargeRecord.setFleetOrderNo(OrderNoUtil.orderNo());
        fleetCardRechargeRecord.setUserPhone(fleetCard.getPhone());
        fleetCardRechargeRecord.setUserName(fleetCard.getContacts());
        return fleetCardRechargeRecordService.insertFleetCardRechargeRecord(fleetCardRechargeRecord);
    }

    // 推送调整余额微信消息
    private void pushMessage(FleetCard updateFleetCard,FleetCardRechargeForm fleetCardRechargeForm){
        SysAppUserInfo appUserInfo = new SysAppUserInfo();
        appUserInfo.setStationId(updateFleetCard.getEnterpriseId());
        appUserInfo.setMobilePhone(updateFleetCard.getPhone());
        SysAppUserInfo sysAppUserInfo = appUserInfoMapper.getOne(appUserInfo);
        if(Objects.isNull(sysAppUserInfo)){
            return;
        }
        // 余额调整消息推送
        BalanceChangeWxNotifyDTO notifyDTO = new BalanceChangeWxNotifyDTO();
        notifyDTO.setEnterpriseId(updateFleetCard.getEnterpriseId().intValue());
        notifyDTO.setOpenId(sysAppUserInfo.getBlogOpenid());
        notifyDTO.setCustomerNo(updateFleetCard.getCardNumber());
        if (CardRechargeRecordEnum.MANUAL_SUB.getValue().equals(fleetCardRechargeForm.getCardType())) {
            notifyDTO.setAmt(fleetCardRechargeForm.getRechargeAmount().negate());
        }else{
            notifyDTO.setAmt(fleetCardRechargeForm.getRechargeAmount());
        }
        notifyDTO.setPresentAmt(fleetCardRechargeForm.getGiftAmount());
        notifyDTO.setBalance(updateFleetCard.getBalance());
//        notifyDTO.setPresentIntegral(integral.getPresentIntegral());
//        notifyDTO.setTotalIntegral(integral.getTotalIntegral());
//        notifyDTO.setStationName(station.getStationName());

        UniversalRedisMessageDto dto=new UniversalRedisMessageDto();
        dto.setData(JSONObject.toJSONString(notifyDTO));
        dto.setMessageType(WxConsumptionMessageEnum.BALANCE_CHANGE_PUSH.getValue());
        dto.setTitle("调整余额 推送公众号信息");
        redisTemplate.convertAndSend(channel, dto);
    }

    @Override
    public List<FleetCardVo> selectFleetCardList(FleetCardQueryForm fleetCardQueryForm) {
        SysUser user = SecurityUtils.getLoginUser().getUser();
        if (SecurityUtils.isPartner()) {
            EnterpriseAndStationVo itemIds = stationService.getItemIds(user);
            if (itemIds != null){
                fleetCardQueryForm.setEnterpriseIdListForAuthor(itemIds.getEnterpriseIds());
            } else {
                throw new CustomException(UserConstants.NO_ENTERPRISE);
            }
        } else {
            fleetCardQueryForm.setEnterpriseId(SecurityUtils.getLoginUser().getUser().getEnterpriseId());
        }
        return fleetCardMapper.selectFleetCardList(fleetCardQueryForm);
    }

    @Override
    public int updateAllocationType(Integer allocationType, Long id) {
        if (ObjectUtils.notEqual(SecurityUtils.getLoginUser().getUser().getUserLevel(), "1"))
            throw new CustomException("请使用油企账号操作！");

        FleetCard fleetCardResult = fleetCardMapper.selectFleetCardById(id);
        if (ObjectUtils.isEmpty(fleetCardResult)) throw new CustomException("记录不存在！");

        if (ObjectUtils.notEqual(fleetCardResult.getUseType(), FleetCard.FLEET_CARD_USE_TYPE_DRIVER))
            throw new CustomException("第三方核销机构不需要分配副卡的额度！");
        List<FleetCardSub> fleetCardSubs = fleetCardSubService.selectByFleetCardId(id);
        BigDecimal subTotal=BigDecimal.ZERO;
        for (FleetCardSub fleetCardSub : fleetCardSubs) {
            if(fleetCardSub.getBalance()!=null){
                subTotal=subTotal.add(fleetCardSub.getBalance());
            }
        }
        if(allocationType.equals(FleetCard.USE_TYPE_SHARE)&&subTotal.compareTo(BigDecimal.ZERO)==1){
            //如果改为主卡共享且子卡余额
            throw new CustomException("当前子卡存在金额未回收，切换失败");
        }



        FleetCard fleetCard = new FleetCard();
        fleetCard.setId(id);
        fleetCard.setSecondaryCardAllocationType(allocationType);
        fleetCard.setUpdatedTime(new Date());
        fleetCard.setUpdatedBy(SecurityUtils.getUsername());
        return fleetCardMapper.updateFleetCard(fleetCard);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public int recovery(Long id) {
        if (ObjectUtils.notEqual(SecurityUtils.getLoginUser().getUser().getUserLevel(), "1"))
            throw new CustomException("请使用油企账号操作！");

        FleetCard fleetCard = fleetCardMapper.selectFleetCardById(id);
        if (ObjectUtils.isEmpty(fleetCard)) throw new CustomException("记录不存在！");

        List<FleetCardSub> fleetCardSubList = fleetCardSubService.selectByFleetCardId(id);
        //if (ObjectUtils.isEmpty(fleetCardSubList)) throw new CustomException("该主卡下没有子卡！");

        for (FleetCardSub fleetCardSub : fleetCardSubList) {
            BigDecimal balance = fleetCardSub.getBalance();
            if (balance.compareTo(BigDecimal.ZERO) == 0) continue;
            //主卡金额直接为0
            //fleetCard.setBalance(fleetCard.getBalance().add(balance));
            fleetCardSub.setBalance(BigDecimal.ZERO);
            fleetCardSub.setUpdatedBy(SecurityUtils.getUsername());
            fleetCardSub.setUpdatedTime(new Date());
            fleetCardSubService.updateFleetCardSub(fleetCardSub);

            // 回收记录
            FleetCardAllocationRecoveryRecord fleetCardAllocationRecoveryRecord = new FleetCardAllocationRecoveryRecord();
            fleetCardAllocationRecoveryRecord.setFleetCardId(id);
            fleetCardAllocationRecoveryRecord.setFleetCardSubId(fleetCardSub.getId());
            fleetCardAllocationRecoveryRecord.setAmount(balance);
            fleetCardAllocationRecoveryRecord.setType(FleetCardAllocationRecoveryRecord.RECOVERY);
            fleetCardAllocationRecoveryRecord.setCreatedBy(SecurityUtils.getUsername());
            fleetCardAllocationRecoveryRecord.setUpdatedBy(SecurityUtils.getUsername());
            fleetCardAllocationRecoveryRecordService.insertFleetCardAllocationRecoveryRecord(fleetCardAllocationRecoveryRecord);
        }

        // 回收记录
        FleetCardAllocationRecoveryRecord fleetCardAllocationRecoveryRecord = new FleetCardAllocationRecoveryRecord();
        fleetCardAllocationRecoveryRecord.setFleetCardId(id);
       // fleetCardAllocationRecoveryRecord.setFleetCardSubId();
        fleetCardAllocationRecoveryRecord.setAmount(fleetCard.getBalance());
        fleetCardAllocationRecoveryRecord.setType(FleetCardAllocationRecoveryRecord.RECOVERY);
        fleetCardAllocationRecoveryRecord.setCreatedBy(SecurityUtils.getUsername());
        fleetCardAllocationRecoveryRecord.setUpdatedBy(SecurityUtils.getUsername());
        fleetCardAllocationRecoveryRecordService.insertFleetCardAllocationRecoveryRecord(fleetCardAllocationRecoveryRecord);

        fleetCard.setBalance(BigDecimal.ZERO);
        fleetCard.setUpdatedBy(SecurityUtils.getUsername());
        fleetCard.setUpdatedTime(new Date());
        return fleetCardMapper.updateFleetCard(fleetCard);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public int deleted(List<Long> ids) {
        ids.forEach(id -> {
            List<FleetCardSub> fleetCardSubList = fleetCardSubService.selectByFleetCardId(id);
            if (ObjectUtils.isNotEmpty(fleetCardSubList)) {
                fleetCardSubList.forEach(fleetCardSub -> {
                    if (fleetCardSub.getBalance().compareTo(BigDecimal.ZERO) > 0)
                        throw new CustomException("子卡存在额度，请先回收！");
                });
                throw new CustomException("存在子卡，主卡不允许删除");
            }


            FleetCard fleetCard = new FleetCard();
            fleetCard.setId(id);
            fleetCard.setDel(System.currentTimeMillis());
            fleetCard.setUpdatedTime(new Date());
            fleetCard.setUpdatedBy(SecurityUtils.getUsername());
            fleetCardMapper.updateFleetCard(fleetCard);
        });
        return 1;
    }

    @Override
    public FleetCard getById(Long id) {
        return fleetCardMapper.selectFleetCardById(id);
    }

    @Override
    public List<FleetCardVo> selectFleetNameList(FleetCardQueryForm fleetCardQueryForm) {
        return fleetCardMapper.selectFleetNameList(fleetCardQueryForm);
    }
}
